C语言基础知识--位运算
1.原码,反码,补码:
(1)在n位的机器数中,最高位为符号位,该位为零表示为正,为一表示为负;其余n-1位为数值位,各位的值可为零或一。当真值为正时,原码、反码、补码数值位 完全相同;当真值为负时,原码的数值位保持原样,反码的数值位是原码数值位的各位取反,补码则是反码的最低位加一。注意符号位不变。
2.无符号位运算
(1)位运算应用口诀
清零取反要用与,某位置一可用或
若要取反和交换,轻轻松松用异或
(2)位运算符的应用 (源操作数s 掩码mask)
按位与-- &:
- 1 清零特定位 (mask中特定位置0,其它位为1,s=s&mask)
- 2 取某数中指定位 (mask中特定位置1,其它位为0,s=s&mask)
按位或-- | :
常用来将源操作数某些位置1,其它位不变。 (mask中特定位置1,其它位为0 s=s|mask)
位异或-- ^ :
使特定位的值取反 (mask中特定位置1,其它位为0 s=s^mask)
(3). 异或运算的一些特性
- 一个数和自己做异或的结果是0。
- 从异或的真值表可以看出,不管是0还是1,和0做异或保持原值不变,和1做异或得到原值的相反值。例如:unsigned int a, b, mask = 1U << 6; a = 0x12345678; b = a ^ mask; /* flip the 6th bit */
- 如果a1^a2^a3……^an之中1的个数为奇数个,否则为偶数个。这条性质可用于奇偶校验(Parity Check)。
- x ^ x ^ y == y 例如:交换两个变量的值,不得借助额外的存储空间a = a ^ b; b = b ^ a; a = a ^ b;
实例说明:
如果要对一个整数中的某些位进行操作,怎样表示这些位在整数中的位置呢?可以用掩码(Mask)来表示。比如掩码0x0000ff00表示对一个32位整数的8~15位进行操作,举例如下。
1、取出8~15位。
unsigned int a, b, mask = 0x0000ff00; a = 0x12345678; b = (a & mask) >> 8; /* 0x00000056 */
这样也可以达到同样的效果:
b = (a >> 8) & ~(~0U << 8);
2、将8~15位清0。
unsigned int a, b, mask = 0x0000ff00; a = 0x12345678; b = a & ~mask; /* 0x12340078 */
3、将8~15位置1。
unsigned int a, b, mask = 0x0000ff00; a = 0x12345678; b = a | mask; /* 0x1234ff78 */